<template>
  <div class="date-tween-wrapper flex">
    <template v-if="options && options.length > 0">
      <el-select v-if="options.length != 1" v-model="_type" style="width: 105px">
        <el-option v-for="item in options" :key="item.value" :label="item.label" :value="item.value" />
      </el-select>
      <div class="single-type color-666 text-[14px] px-3" v-else>{{ options[0].label }}</div>
    </template>
    <el-date-picker
      v-model="_date"
      type="daterange"
      value-format="YYYY-MM-DD"
      start-placeholder="开始日期"
      range-separator="至"
      end-placeholder="结束日期"
      :shortcuts="_shortcuts"
      :editable="false"
      v-bind="$attrs"
      style="width: 250px"
      @change="(val: Array<Options>) => emit('change', val)"
    />
  </div>
</template>

<script setup lang="ts">
import { PropType } from 'vue'

type Options = {
  label: string
  value: string
}
type ShortcutsType = '今日' | '昨日' | '本周' | '上周' | '本月' | '上月' | '今年'
type Shortcuts = {
  text: ShortcutsType
  value: () => Date[]
}[]

const shortcuts: Shortcuts = [
  {
    text: '今日',
    value: () => {
      const today = new Date()
      return [today, today]
    },
  },
  {
    text: '昨日',
    value: () => {
      const yesterday = new Date()
      yesterday.setDate(yesterday.getDate() - 1)
      return [yesterday, yesterday]
    },
  },
  {
    text: '本周',
    value: () => {
      const today = new Date()
      const startOfWeek = new Date(today)
      startOfWeek.setDate(startOfWeek.getDate() - startOfWeek.getDay())
      const endOfWeek = new Date(startOfWeek)
      endOfWeek.setDate(endOfWeek.getDate() + 6)
      return [startOfWeek, endOfWeek]
    },
  },
  {
    text: '上周',
    value: () => {
      const today = new Date()
      const startOfWeek = new Date(today)
      startOfWeek.setDate(startOfWeek.getDate() - startOfWeek.getDay() - 7)
      const endOfWeek = new Date(startOfWeek)
      endOfWeek.setDate(endOfWeek.getDate() + 6)
      return [startOfWeek, endOfWeek]
    },
  },
  {
    text: '本月',
    value: () => {
      const today = new Date()
      const startOfMonth = new Date(today.getFullYear(), today.getMonth(), 1)
      const endOfMonth = new Date(today.getFullYear(), today.getMonth() + 1, 0)
      return [startOfMonth, endOfMonth]
    },
  },
  {
    text: '上月',
    value: () => {
      const today = new Date()
      const startOfMonth = new Date(today.getFullYear(), today.getMonth(), 1)
      startOfMonth.setMonth(startOfMonth.getMonth() - 1)
      const endOfMonth = new Date(startOfMonth.getFullYear(), startOfMonth.getMonth() + 1, 0)
      return [startOfMonth, endOfMonth]
    },
  },
  {
    text: '今年',
    value: () => {
      const today = new Date()
      const startOfYear = new Date(today.getFullYear(), 0, 1)
      const endOfYear = new Date(today.getFullYear(), 11, 31)
      return [startOfYear, endOfYear]
    },
  },
]

defineOptions({
  name: 'DateTween',
})

const props = defineProps({
  modelValue: {
    type: Array as PropType<Array<string>>,
    default: () => [],
  },
  type: {
    type: String,
    default: '',
  },
  options: {
    type: Array as PropType<Array<Options>> | undefined,
    default: undefined,
  },
  shortcutsList: {
    type: Array as PropType<Array<ShortcutsType>>,
    default: () => [],
  },
})

const emit = defineEmits(['update:modelValue', 'update:type', 'change'])

const _date = useVModel(props, 'modelValue', emit)
const _type = useVModel(props, 'type', emit)

const _shortcuts = computed(() => shortcuts.filter(item => props.shortcutsList.includes(item.text)))
</script>

<style lang="scss" scoped>
.date-tween-wrapper {
  .single-type {
    display: grid;
    place-items: center;
    border-radius: var(--el-border-radius-base);
    border-top-right-radius: 0;
    border-bottom-right-radius: 0;
    box-shadow: 0 0 0 1px var(--el-border-color) inset;
    transform: translateX(1px);
  }
  :deep(.el-select__wrapper) {
    border-top-right-radius: 0;
    border-bottom-right-radius: 0;
  }
  :deep(.el-input__wrapper) {
    border-top-left-radius: 0;
    border-bottom-left-radius: 0;
  }
}
</style>
